package com.lbw.Client.rpcClient.impl;


import com.lbw.Client.netty.nettyInitalizer.NettyClientInitializer;
import com.lbw.Client.rpcClient.RpcClient;
import com.lbw.Client.serviceCenter.ServiceCenter;
import com.lbw.Client.serviceCenter.ZKServiceCenter;
import com.lbw.Message.RpcRequest;
import com.lbw.Message.RpcResponse;
import com.lbw.Server.provider.ServiceProvider;
import io.netty.bootstrap.Bootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelFuture;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioSocketChannel;
import io.netty.util.AttributeKey;
import lombok.AllArgsConstructor;

import java.net.InetSocketAddress;

/**
 * @author lbwxxc
 * @date 2025/2/19 16:44
 * @description: TODO
 */
@AllArgsConstructor
public class NettyRpcClient implements RpcClient {
    private ServiceProvider serviceProvider;
    private ServiceCenter serviceCenter;
    private static final Bootstrap bootstrap;
    private static final EventLoopGroup eventLoopGroup;

    public NettyRpcClient() throws InterruptedException {
        serviceCenter = new ZKServiceCenter();
    }

    static {
        eventLoopGroup = new NioEventLoopGroup();
        bootstrap = new Bootstrap();
        bootstrap.group(eventLoopGroup).channel(NioSocketChannel.class)
                .handler(new NettyClientInitializer());
    }


    @Override
    public RpcResponse sendRequest(RpcRequest request) {
        //从注册中心回调地址和端口
        InetSocketAddress address = serviceCenter.serviceDiscovery(request.getInterfaceName());
        String host = address.getHostName();
        int port = address.getPort();
        System.out.println("服务地址：" + host + ":" + port);
        try {
            ChannelFuture channelFuture = bootstrap.connect(host, port).sync();
            Channel channel = channelFuture.channel();
            channel.writeAndFlush(request);
            System.out.println("数据发送成功" + request);
            channel.closeFuture().sync();
            AttributeKey<RpcResponse> key = AttributeKey.valueOf("RPCResponse");
            RpcResponse response = channel.attr(key).get();
            System.out.println(response);
            return response;
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return null;
    }
}
